; PLAZMA.ASM
; Source code 4	TASM 3.1 sysop:	Nikonov	Mike 2002 aka Wcd@Nail (JNCsoft)
; Translate from C++ 3.1
; Plasma & Text

.MODEL	Small
.STACK	100h
;Direct		 EQU 0	 ; direction output (during calculation)

GetCh	MACRO
	xor	AH,AH
	int	16h
	ENDM

; Table	One 4 Cirlce
TabSeg1	SEGMENT	'BSS'
DB	64000 dup (?)
TabSeg1	ENDS

; Table	Two 4 Circle
TabSeg2	SEGMENT	'BSS'
DB	64000 dup (?)
TabSeg2	ENDS

IFNDEF	Direct
BodySeg	SEGMENT	'BSS'
DB	64000 dup (?)
BodySeg	ENDS
ENDIF

; Picture segment
PictSeg	SEGMENT	'BSS'
DB	64004 dup (?)
PictSeg	ENDS

.DATA
; 4 Tables
Adder		DD 16.0	; must be 16.0
Four		DD 4.0	; 4.0
Five		DD 5.0	; 5.0
Nine_Half	DD 9.5	; 9.5 scale
NineTee		DD 90.0	; 90.0 concentration
; 4 Colors
Red		DQ 0.5235987668
Green		DQ 1.5707963
Blue		DQ 2.6179938332
iRed		DQ 0.05
iGreen		DQ 0.05
iBlue		DQ 0.1
DivIt		DW 256
MultiIt		DW 31
TPi		DQ ?
; 4 Plazzzma :)
hWidth		DW 80
hHeight		DW 50
x1		DD 159
y1		DD 48
x2		DD 81
y2		DD 99
x3		DD 159
y3		DD 48
x4		DD 159
y4		DD 49
roll		DD 0
circle1		DD 0
circle2		DD 0
circle3		DD 0
circle4		DD 0
circle5		DD 0
circle6		DD 0
circle7		DD 0
circle8		DD 0
icirc1		DQ 0.01416667
icirc2		DQ 0.01666667
icirc3		DQ 0.05
icirc4		DQ 0.03333334
icirc5		DQ 0.06666667
icirc6		DQ 0.025
icirc7		DQ 0.05833333
icirc8		DQ 0.00833334
; Other
Temp		DW ?
Temp32		DD ?
TempR		DQ ?
; 4 Picture
FileName	DB 'TEXT.R13',0
NoFileMessage	DB 13,10,7,'File TEXT.R13 not found or bad.',13,10,'$'
picx		DD 0
picy		DD 0
picc		DW 0
fWidth		DW ?
fHeight		DW ?

.CODE
.386

LoadR13	PROC
	push	DS
	mov	AH,3Dh	; open file
	xor	AL,AL	; 4 read
	mov	DX,offset FileName
	int	21h
	jc	@@NoFile
	mov	BX,AX	; descr
	mov	AH,3Fh	; read width & height
	mov	CX,4	; 4 bytes
	mov	DX,offset fWidth
	int	21h	; do it
	mov	AX,PictSeg
	mov	DS,AX
	xor	DX,DX
	mov	AH,3Fh	; read bitmap
	mov	CX,64000; file length
	int	21h
	mov	AH,3Eh	; close	file
	int	21h
	jmp	@@Normal
@@NoFile:
	pop	DS
	mov	AH,09h
	mov	DX,offset NoFileMessage
	int	21h
	mov	AX,4C01h
	int	21h
@@Normal:
	pop	DS
	ret
	ENDP

InitTables PROC	near
	pushad
	mov	AX,TabSeg1
	mov	FS,AX
	mov	AX,TabSeg2
	mov	GS,AX
	xor	DI,DI
	xor	EBX,EBX	; i
	xor	EBP,EBP	; j
@@Filling1:
	; Table	One
	mov	EAX,100	; pHeight
	sub	EAX,EBX	; pHeight-i
	mov	ECX,EAX
	imul	ECX	; (pHeight-i)^2
	mov	[Temp32],EAX
	fild	[Temp32]
	mov	EAX,160	; pWidth
	sub	EAX,EBP	; pWidth-j
	mov	ECX,EAX
	imul	ECX	; (pWidth-j)^2
	mov	[Temp32],EAX
	fiadd	[Temp32]; (pWidth-j)^2+(pHeight-i)^2
	fadd	[Adder]	; 16.0+(pHeight-i)^2+(pWidth-j)^2
	fsqrt
	fsub	[Four]
	fst	[TempR]
	fmul	[Five]
	fistp	[Temp32]
	mov	EAX,[Temp32]
	mov	FS:[DI],AL
	; Table	Two
	fld	[TempR]
	fdiv	[Nine_Half]
	fsin
	fld1
	fadd
	fmul	[NineTee]
	fistp	[Temp32]
	mov	EAX,[Temp32]
	mov	GS:[DI],AL
	; j++
	inc	EBP
	cmp	EBP,320
	jb	@@Next
	xor	EBP,EBP	; j=0;
	inc	EBX	; i++;
@@Next:
	inc	DI
	cmp	EBX,200
	jb	@@Filling1
	popad
	ret
	ENDP

Init	PROC
	mov	AX,@DATA
	mov	DS,AX
	; calc 2*pi
	finit
	fld1
	fld1
	fadd
	fldpi
	fmul
	fstp	[TPi]
	; Init table one & two
	call	InitTables
	call	LoadR13
	; Set 320x200x256 color	VGA mode
	mov	AX,0013h
	int	10h
	ret
	ENDP

SetAllPalette PROC
	xor	CX,CX	; i=0;
	finit
@@Colors:
	mov	AX,CX	; AL = color
	mov	DX,3C8h	; DAC Write
	out	DX,AL	; set that
	inc	DX	; DAC Data
	mov	[Temp],CX; i
	fld	[TPi]
	fidiv	[DivIt]	; 2*pi/256
	fimul	[Temp]	; 2*pi/256*i
	fstp	[TempR]	; pop up
	; Red
	fld	[Red]
	fadd	[TempR]
	fcos
	fld1
	fadd
	fimul	[MultiIt]
	fistp	[Temp]
	mov	AX,[Temp]
	out	DX,AL
	; Green
	fld	[Green]
	fadd	[TempR]
	fcos
	fld1
	fadd
	fimul	[MultiIt]
	fistp	[Temp]
	mov	AX,[Temp]
	out	DX,AL
	; Blue
	fld	[Blue]
	fadd	[TempR]
	fcos
	fld1
	fadd
	fimul	[MultiIt]
	fistp	[Temp]
	mov	AX,[Temp]
	out	DX,AL
	inc	CX	; i++;
	cmp	CX,256	; while(i<256);
	jb	@@Colors
	; Red+=iRed;
	fld	[Red]
	fadd	[iRed]
	fstp	[Red]
	; Green-=iGreen;
	fld	[Green]
	fsub	[iGreen]
	fstp	[Green]
	; Blue+=iBlue
	fld	[Blue]
	fadd	[iBlue]
	fstp	[Blue]
	ret
	ENDP

CalcBody PROC
	mov	AX,TabSeg1
	mov	FS,AX
	mov	AX,TabSeg2
	mov	GS,AX
IFNDEF	Direct
	mov	AX,BodySeg
ELSE
	mov	AX,0A000h
ENDIF
	mov	ES,AX
	xor	DI,DI
	xor	EBX,EBX	; i
	xor	ECX,ECX	; j
@@FillBody:
	mov	EAX,[y1]	; y1
	add	EAX,EBX		; i+y1
	imul	EAX,320		; 320*(i+y1)
	add	EAX,ECX		; 320*(i+y1)+j
	add	EAX,[x1]	; 320*(i+y1)+j+x1
	mov	ESI,EAX
IFNDEF	Direct
	mov	AL,FS:[SI]
	mov	ES:[DI],AL	; body[DI]=tab1[320*(i+y1)+j+x1]
ELSE
	mov	AX,FS:[SI]
	mov	ES:[DI],AX
	mov	ES:[DI+320],AX
ENDIF
	mov	EAX,[roll]
IFNDEF	Direct
	add	ES:[DI],AL	; +roll
ELSE
	add	ES:[DI],AX
	add	ES:[DI+320],AX
ENDIF
	mov	EAX,[y2]
	add	EAX,EBX
	imul	EAX,320
	add	EAX,ECX
	add	EAX,[x2]
	mov	ESI,EAX
IFNDEF	Direct
	mov	AL,GS:[SI]
	add	ES:[DI],AL	;+tab2[320*(i+y2)+j+x2]
ELSE
	mov	AX,GS:[SI]
	add	ES:[DI],AX
	add	ES:[DI+320],AX
ENDIF
	mov	EAX,[y3]
	add	EAX,EBX
	imul	EAX,320
	add	EAX,ECX
	add	EAX,[x3]
	mov	ESI,EAX
IFNDEF	Direct
	mov	AL,GS:[SI]
	add	ES:[DI],AL	;+tab2[320*(i+y3)+j+x3]
ELSE
	mov	AX,GS:[SI]
	add	ES:[DI],AX
	add	ES:[DI+320],AX
ENDIF
	mov	EAX,[y4]
	add	EAX,EBX
	imul	EAX,320
	add	EAX,ECX
	add	EAX,[x4]
	mov	ESI,EAX
IFNDEF	Direct
	mov	AL,GS:[SI]
	add	ES:[DI],AL	;+tab2[320*(i+y4)+j+x4]
ELSE
	mov	AX,GS:[SI]
	add	ES:[DI],AX
	add	ES:[DI+320],AX
ENDIF
	mov	EAX,[picy]	; picy
	add	EAX,EBX		; i+picy
	imul	EAX,320		; 320*(i+picy)
	add	EAX,ECX		; 320*(i+picy)+j
	add	EAX,[picx]	; 320*(i+picy)+j+picx
	add	EAX,4		; 320*(i+picy)+j+picx+4
	mov	ESI,EAX
	push	FS
	mov	AX,PictSeg
	mov	FS,AX
IFNDEF	Direct
	mov	AL,FS:[SI]
	add	ES:[DI],AL
	inc	DI
ELSE
	mov	AX,FS:[SI]
	add	ES:[DI],AX
	add	DI,2
ENDIF
	pop	FS
	inc	ECX
	cmp	ECX,160
	jb	@@FillBody
IFDEF	Direct
	add	DI,320
ENDIF
	xor	ECX,ECX
	inc	EBX
	cmp	EBX,100
	jb	@@FillBody
IFDEF	Direct
	call	VSync
ENDIF
	ret
	ENDP

CalcCoords PROC
	finit
	;x1
	fld	dword ptr [circle3]
	fadd	qword ptr [icirc3]
	fst	dword ptr [circle3]
	fcos
	fimul	word ptr [hWidth]
	fiadd	word ptr [hWidth]
	fistp	dword ptr [x1]
	;y1
	fld	dword ptr [circle4]
	fsub	qword ptr [icirc4]
	fst	dword ptr [circle4]
	fsin
	fimul	word ptr [hHeight]
	fiadd	word ptr [hHeight]
	fistp	dword ptr [y1]
	;x2
	fld	dword ptr [circle1]
	fadd	qword ptr [icirc1]
	fst	dword ptr [circle1]
	fsin
	fimul	word ptr [hWidth]
	fiadd	word ptr [hWidth]
	fistp	dword ptr [x2]
	;y2
	fld	dword ptr [circle2]
	fsub	qword ptr [icirc2]
	fst	dword ptr [circle2]
	fcos
	fimul	word ptr [hHeight]
	fiadd	word ptr [hHeight]
	fistp	dword ptr [y2]
	;x3
	fld	dword ptr [circle5]
	fadd	qword ptr [icirc5]
	fst	dword ptr [circle5]
	fcos
	fimul	word ptr [hWidth]
	fiadd	word ptr [hWidth]
	fistp	dword ptr [x3]
	;y3
	fld	dword ptr [circle6]
	fsub	qword ptr [icirc6]
	fst	dword ptr [circle6]
	fsin
	fimul	word ptr [hHeight]
	fiadd	word ptr [hHeight]
	fistp	dword ptr [y3]
	;x4
	fld	dword ptr [circle7]
	fadd	qword ptr [icirc7]
	fst	dword ptr [circle7]
	fcos
	fimul	word ptr [hWidth]
	fiadd	word ptr [hWidth]
	fistp	dword ptr [x4]
	;y4
	fld	dword ptr [circle8]
	fsub	qword ptr [icirc8]
	fst	dword ptr [circle8]
	fsin
	fimul	word ptr [hHeight]
	fiadd	word ptr [hHeight]
	fistp	dword ptr [y4]
	fwait
	add	dword ptr [roll],5
	ret
	ENDP

UpDatePic PROC
	cmp	word ptr [picc],100
	ja	@@n0
	inc	word ptr [picc]
	jmp	@@return
@@n0:
	cmp	word ptr [picc],150
	ja	@@n1
	inc	word ptr [picc]
	add	dword ptr [picy],2
	jmp	@@return
@@n1:
	cmp	word ptr [picc],250
	ja	@@n2
	inc	word ptr [picc]
	jmp	@@return
@@n2:
	cmp	word ptr [picc],330
	ja	@@n3
	inc	word ptr [picc]
	add	dword ptr [picx],2
	jmp	@@return
@@n3:
	cmp	word ptr [picc],430
	ja	@@n4
	inc	word ptr [picc]
	jmp	@@return
@@n4:
	cmp	word ptr [picc],480
	ja	@@n5
	inc	word ptr [picc]
	sub	dword ptr [picy],2
	jmp	@@return
@@n5:
	cmp	word ptr [picc],580
	ja	@@n6
	inc	word ptr [picc]
	jmp	@@return
@@n6:
	cmp	word ptr [picc],660
	ja	@@n7
	inc	word ptr [picc]
	sub	dword ptr [picx],2
	jmp	@@return
@@n7:
	mov	word ptr [picc],0
@@return:
	ret
	ENDP

IFNDEF	Direct

OutBody	PROC
	push	DS
	push	ES
	mov	AX,0A000h
	mov	ES,AX
	xor	DI,DI
	xor	SI,SI
	mov	AX,BodySeg
	mov	DS,AX
	xor	DX,DX
	xor	BX,BX
	mov	CX,100
@@loop1:
	mov	DX,160
@@loop2:
	mov	AL,[SI]
	mov	AH,AL
	mov	ES:[DI],AX
	inc	DI
	inc	DI
	inc	SI
	dec	DX
	jg	@@loop2
	add	DI,BX
	sub	SI,160
	mov	DX,160
@@loop3:
	mov	AL,[SI]
	mov	AH,AL
	mov	ES:[DI],AX
	inc	DI
	inc	DI
	inc	SI
	dec	DX
	jg	@@loop3
	add	DI,BX
	loop	@@loop1
	pop	ES
	pop	DS
	ret
	ENDP

OutSeg	PROC
	push	SI DI AX CX ES DS
	push	0A000h
	pop	ES
	mov	DS,AX
	xor	SI,SI
	xor	DI,DI
	mov	CX,16000
	rep	movsd
	pop	DS ES CX AX DI SI
	ret
	ENDP

ENDIF

Main	PROC
	call	Init
	call	SetAllPalette

@@GoGo:
	call	CalcCoords
	call	CalcBody
	call	UpDatePic
	call	SetAllPalette
IFNDEF	Direct
	call	VSync
	call	OutBody
ENDIF
	mov	AH,01h
	int	16h
	jz	@@GoGo
	GetCh

	mov	AX,0003h
	int	10h
	mov	AX,4C00h
	int	21h
	ENDP

VSync	PROC
	mov	DX,03DAh
@@WaitNotVSync:
	in	AL,DX
	and	AL,8
	jnz	@@WaitNotVSync
@@WaitVSync:
	in	AL,DX
	and	AL,8
	jz	@@WaitVSync
	ret
	ENDP

	END	Main
